#include <learn/check_gl.h>
#include <learn/gl/gl_callback.h>

#include <algorithm>
#include <array>
#include <iostream>
#include <numeric>
#include <random>
#include <vector>

using namespace xi::gl;

void init_scale()
{
    // 纹理图案和缩略图案
    float texArray16[16][16][4];
    float texArray8[8][8][4];
    float texArray4[4][4][4];
    float texArray2[2][2][4];
    float texArray1[1][1][4];

    // 激活纹理
    glEnable(GL_TEXTURE_2D);

    // 16 x 16
    for (int i = 0; i < 16; i++)
    {
        for (int j = 0; j < 16; j++)
        {
            texArray16[i][j][0] = 1;
            texArray16[i][j][1] = 0;
            texArray16[i][j][2] = 0;
            texArray16[i][j][3] = 1;
        }
    }
    for (int i = 0; i < 8; i++)
    {
        for (int j = 0; j < 8; j++)
        {
            texArray8[i][j][0] = 1;
            texArray8[i][j][1] = 1;
            texArray8[i][j][2] = 0;
            texArray8[i][j][3] = 1;
        }
    }
    for (int i = 0; i < 4; i++)
    {
        for (int j = 0; j < 4; j++)
        {
            texArray4[i][j][0] = 0;
            texArray4[i][j][1] = 1;
            texArray4[i][j][2] = 0;
            texArray4[i][j][3] = 1;
        }
    }
    for (int i = 0; i < 2; i++)
    {
        for (int j = 0; j < 2; j++)
        {
            texArray2[i][j][0] = 0;
            texArray2[i][j][1] = 0;
            texArray2[i][j][2] = 1;
            texArray2[i][j][3] = 1;
        }
    }
    for (int i = 0; i < 1; i++)
    {
        for (int j = 0; j < 1; j++)
        {
            texArray1[i][j][0] = 1;
            texArray1[i][j][1] = 1;
            texArray1[i][j][2] = 1;
            texArray1[i][j][3] = 1;
        }
    }

    // 指定用缩略图纹理填充的边界过滤模式
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);

    // 指定纹理层级
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 16, 16, 0, GL_RGBA, GL_FLOAT, texArray16);
    glTexImage2D(GL_TEXTURE_2D, 1, GL_RGBA, 8, 8, 0, GL_RGBA, GL_FLOAT, texArray8);
    glTexImage2D(GL_TEXTURE_2D, 2, GL_RGBA, 4, 4, 0, GL_RGBA, GL_FLOAT, texArray4);
    glTexImage2D(GL_TEXTURE_2D, 3, GL_RGBA, 2, 2, 0, GL_RGBA, GL_FLOAT, texArray2);
    glTexImage2D(GL_TEXTURE_2D, 4, GL_RGBA, 1, 1, 0, GL_RGBA, GL_FLOAT, texArray1);
}

void render_scale()
{
    // 这里纹理映射从 0 到 10 是为了让纹理更密集，从而使缩略纹理能够更快出现
    glBegin(GL_QUADS);
    glTexCoord2f(0, 0);
    glVertex3f(-2.0, -1.0, 0);
    glTexCoord2f(10, 0);
    glVertex3f(-2.0, 1.0, 0);
    glTexCoord2f(10, 10);
    glVertex3f(2000.0, 1.0, -6000.0);
    glTexCoord2f(0, 10);
    glVertex3f(2000.0, -1.0, -6000.0);
    glEnd();
}

void init_chess()
{
    // 指定 16 x 16 颜色纹理
    float texArray[16][16][4];
    for (int i = 0; i < 16; i++)
    {
        for (int j = 0; j < 16; j++)
        {
            if ((i + j) % 2 == 0)
            {
                texArray[i][j][0] = 1;
                texArray[i][j][1] = 1;
                texArray[i][j][2] = 1;
                texArray[i][j][3] = 1;
            }
            else
            {
                texArray[i][j][0] = 0;
                texArray[i][j][1] = 0;
                texArray[i][j][2] = 0;
                texArray[i][j][3] = 1;
            }
        }
    }

    // 指定边界混合模式
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);

    // 指定二维纹理图像
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 16, 16, 0, GL_RGBA, GL_FLOAT, texArray);

    // 激活纹理
    glEnable(GL_TEXTURE_2D);

    // 设置自动生成纹理
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

    glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_OBJECT_LINEAR);
    glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_OBJECT_LINEAR);

    glEnable(GL_TEXTURE_GEN_S);
    glEnable(GL_TEXTURE_GEN_T);
}

void render_chess()
{
    // 绘制四边形
    glBegin(GL_QUADS);
    glVertex3f(0, 0, 0);
    glVertex3f(1, 0, 0);
    glVertex3f(1, 2, 0);
    glVertex3f(0, 2, 0);
    glEnd();
}

void init()
{
    glEnable(GL_DEPTH_TEST);
    glClearColor(0.0f, 0.0f, 0.0f, 1.0f);

    // init_scale();
    init_chess();
}

void render()
{
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    // render_scale();
    render_chess();
}

int main()
{
    if (!glfwInit())
    {
        std::cerr << "Failed to initialize GLFW" << std::endl;
        return -1;
    }

    GLFWwindow *window = glfwCreateWindow(800, 600, "Three Stars", nullptr, nullptr);
    if (!window)
    {
        std::cerr << "Failed to create GLFW window" << std::endl;
        glfwTerminate();
        return -1;
    }
    glfwMakeContextCurrent(window);

    // 注册函数
    glfwSetFramebufferSizeCallback(window, GLFWWindowResize);
    glfwSetScrollCallback(window, GLFWScrollCallback);
    glfwSetMouseButtonCallback(window, GLFWMouseButtonCallback);
    glfwSetCursorPosCallback(window, GLFWCursorPosCallback);
    glfwSetKeyCallback(window, GLFWKeyCallback);
    glfwSetDropCallback(window, GLFWDropCallback);

    init();
    while (!glfwWindowShouldClose(window))
    {
        // 视图变换
        transform(window);

        render();
        glfwSwapBuffers(window);
        glfwPollEvents();
    }

    glfwTerminate();

    return 0;
}
